#include <QApplication>

#include <itkImage.h>
#include <itkImageFileReader.h>
#include <itkInvertIntensityImageFilter.h>
#include <itkSubtractImageFilter.h>

#include "DGVImageVTK.h"
#include "itkImageToVTKImageFilter.h"

typedef float PixelType;
typedef itk::Image<PixelType,2> ImageType;
typedef itk::ImageFileReader< ImageType >  ReaderType;
typedef itk::InvertIntensityImageFilter< ImageType >  InvertorType;
typedef itk::SubtractImageFilter< ImageType >  SubtractType;
typedef itk::ImageToVTKImageFilter< ImageType >  ConnectorType;

int main(int argc, char *argv[])
{
	QApplication app(argc,argv);

	if(argc == 3)
	{
	    ///----------
	    ///Read First Image
	    bool success = false;
	    int bounds[6];

        ///Read
        ReaderType::Pointer reader = ReaderType::New();
            reader->SetFileName(argv[1]);
            reader->Update();

        ///Invert image
//        InvertorType::Pointer invertor = InvertorType::New();
//            invertor->SetInput( reader->GetOutput() );
//            invertor->Update();
//            invertor->Print(cerr);

	    ///Export to VTK
	    ConnectorType::Pointer connector = ConnectorType::New();
            connector->SetInput( reader->GetOutput() );
            connector->Update();
            connector->GetOutput()->GetExtent(bounds);
            cout << "Size: " << bounds[1] << "x" << bounds[3] << endl;

        ///Display
        DGVImageVTK *image1 = new DGVImageVTK;
            image1->alignImages(false); //Has no effect?
            image1->SetInput(connector->GetOutput());
            image1->generateImage();
            image1->show();

        ///----------
	    ///Read Second Image
	    ReaderType::Pointer reader2 = ReaderType::New();
            reader2->SetFileName(argv[2]);
            reader2->Update();

        ///Invert image
//        InvertorType::Pointer invertor2 = InvertorType::New();
//            invertor2->SetInput( reader2->GetOutput() );
//            invertor2->Update();

        ///Export to VTK
        ConnectorType::Pointer connector2 = ConnectorType::New();
            connector2->SetInput( reader2->GetOutput() );
            connector2->Update();
            connector2->GetOutput()->GetExtent(bounds);
            cout << "Size: " << bounds[1] << "x" << bounds[3] << endl;

        ///Display
        DGVImageVTK *image2 = new DGVImageVTK;
            image2->alignImages(false); //Has no effect?
            image2->SetInput(connector2->GetOutput());
            image2->generateImage();
            image2->show();

        ///----------
        ///Subtract Images
        SubtractType::Pointer subtractor = SubtractType::New();
            subtractor->SetInput1( reader->GetOutput() );
            subtractor->SetInput2( reader2->GetOutput() );
            subtractor->Update();

        ///Export to VTK
        ConnectorType::Pointer connector3 = ConnectorType::New();
            connector3->SetInput( subtractor->GetOutput() );
            connector3->Update();
            connector3->GetOutput()->GetExtent(bounds);
            cout << "Size: " << bounds[1] << "x" << bounds[3] << endl;

        ///Display
        DGVImageVTK *image3 = new DGVImageVTK;
            image3->alignImages(false); //Has no effect?
            image3->SetInput(connector3->GetOutput());
            image3->generateImage();
            image3->show();

		success = app.exec();

        //Smart pointer handles deletion

		return EXIT_SUCCESS;
	}
	else
	{
		cerr << "Error in Filename. Aborting." << endl;
		return EXIT_FAILURE;
	}
}

/**
    typedef itk::SubtractImageFilter< ImageType >  SubtractType;

    SubtractType::Pointer subtractor = SubtractType::New();
        subtractor->SetInput1(image1);
        subtractor->SetInput2(image2);
        subtractor->Update();

    connector->SetInput( reader->GetOutput() );
        connector->Update();

    image.SetInput(connector->GetOutput());
        image.generateImage();
		image.show();
*/
